import { EventConfig } from "../SysConfig/SysConfig";
import EventManage from "./EventManage";


const { ccclass, property } = cc._decorator;

enum WebState {
    Disconnect = 0, // 断开连接
    Connecting = 1, // 正在连接
    Connected = 2,  // 已经连接;
};

@ccclass
export class NetManage extends cc.Component {
    public static Instance: NetManage = null;

    private m_webState: WebState = null;
    private m_webSocket: WebSocket = null;
    private m_serveUrl: string = 'ws://127.0.0.1:8080';


    onLoad(): void {
        if (NetManage.Instance === null) {
            NetManage.Instance = this;
        }
        else {
            this.destroy();
            return;
        }
    }

    init(_serveUrl: string) {
        this.m_serveUrl = _serveUrl;
    }

    start(): void {
        this.m_webState = WebState.Disconnect;
        this.connect_to_server();
    }

    private connect_to_server(): void {
        if (this.m_webState != WebState.Disconnect) {
            return;
        }
        this.m_webState = WebState.Connecting;
        // 抛出一个正在重新连接的事件;
        // EventMgr.Instance.Emit("net_connecting", null);

        this.m_webSocket = new WebSocket(this.m_serveUrl);  // H5标准，底层做好了;
        this.m_webSocket.binaryType = "arraybuffer";        // blob或二进制;

        this.m_webSocket.onopen = this._on_socket_open.bind(this);
        this.m_webSocket.onmessage = this._on_socket_message.bind(this);
        this.m_webSocket.onclose = this._on_socket_close.bind(this);
        this.m_webSocket.onerror = this._on_socket_error.bind(this);
    }


    // 连接成功回调
    private _on_socket_open(event: Event) {
        this.m_webState = WebState.Connected;
        console.log("connect to server: " + this.m_serveUrl + " sucess!");
        console.log('链接成功！！！', event)

        // EventManage.Instance.dispatchEvent("net_connect", null);
    }

    // 收到消息回调
    private _on_socket_message(event: MessageEvent) {
        console.log('收到服务器消息：', event.data)

        EventManage.Instance.dispatchEvent(EventConfig.Net_Message, event.data);
    }

    // 关闭链接回调
    private _on_socket_close(event: CloseEvent) {
        console.log('关闭链接：', event)
        this.closeSocket();
    }

    // 连接错误回调
    private _on_socket_error(event: Event) {
        console.log('错误链接：', event)
        this.closeSocket();
    }

    // 心跳
    /**websocket长连接有默认的超时时间（1分钟），也就是说，超过一定的时间客户端和服务器之间没有发生任何消息传输，连接会自动断开；除此之外，服务器或防火墙一般也会在一段时间不活动并超时之后终止外部的长连接。因此，若需要使客户端一直保持连接，就需要设置心跳保活机制了。 */
    private _heartBeat(): void {

    }


    private m_interval1: number = 0;
    private m_interval2: number = 0;
    update(dt: number) {
        //2秒尝试一次断线重连
        this.m_interval1 += dt;
        if (this.m_interval1 > 2) {
            this.m_interval1 = 0;
            this.connect_to_server();
        }

        //20秒心跳测试
        this.m_interval2 += dt;
        if (this.m_interval2 >= 20) {
            this.m_interval2 = 0;
            this._heartBeat();
        }
    }



    /**关闭Socket的链接 */
    public closeSocket() {
        if (this.m_webState === WebState.Connected) {
            if (this.m_webSocket !== null) {
                this.m_webSocket.close();
                this.m_webSocket = null;
            }
        }

        this.m_interval1 = 0;
        this.m_interval2 = 0;

        this.m_webState = WebState.Disconnect;

        // EventManage.Instance.dispatchEvent("net_disconnect", null);
    }

    /**发送数据 */
    public sendData(arraybuf: ArrayBuffer | string) {
        if (this.m_webSocket && this.m_webState == WebState.Connected) {
            this.m_webSocket.send(arraybuf);
        }
        else {
            console.log('webSocket初始化异常!!!')
        }
    }
}
